//`define TEST_FIRST
module fragment_gen_checker(
    input clk,
    input rst_n_in,
    output reg 		 busy,                             //input busy
    output reg 		 bte_start,                        //input traversal start
    output reg  [31:0] tile_x,                           //input cur tile left-bottom x coordinate, fixed 16.16
    output reg  [31:0] tile_y,                           //input cur tile left-bottom y coordinate, fixed 16.16 
    output reg  [47:0] vertex0_x               ,         //input vertex0 x coordinate, fixed 1.31.16
    output reg  [47:0] vertex0_y               ,         //input vertex0 x coordinate, fixed 1.31.16
    output reg  [47:0] vertex0_z               ,         //input vertex0 x coordinate, fixed 1.31.16
    output reg  [47:0] vertex0_w               ,         //input vertex0 x coordinate, fixed 1.31.16
    output reg  [31:0] vertex0_s0              ,         //input vertex0 x coordinate, fixed 1.15.16
    output reg  [31:0] vertex0_t0              ,         //input vertex0 x coordinate, fixed 1.15.16
    output reg  [31:0] vertex0_r0              ,         //input vertex0 x coordinate, fixed 1.15.16
    output reg  [31:0] vertex0_q0              ,         //input vertex0 x coordinate, fixed 1.15.16
    output reg  [7:0]  vertex0_primary_r       ,
    output reg  [7:0]  vertex0_primary_g      ,
    output reg  [7:0]  vertex0_primary_b      ,
    output reg  [7:0]  vertex0_primary_a      ,
    output reg  [31:0] vertex0_fog_x          ,
    output reg  [31:0] vertex0_fog_y          ,
    output reg  [31:0] vertex0_fog_z          ,
    output reg  [31:0] vertex0_fog_w          ,
    output reg  [47:0] vertex1_x               ,
    output reg  [47:0] vertex1_y               ,
    output reg  [47:0] vertex1_z               ,
    output reg  [47:0] vertex1_w               ,
    output reg  [31:0] vertex1_s0              ,
    output reg  [31:0] vertex1_t0              ,
    output reg  [31:0] vertex1_r0              ,
    output reg  [31:0] vertex1_q0              ,
    output reg  [7:0]  vertex1_primary_r       ,
    output reg  [7:0]  vertex1_primary_g      ,
    output reg  [7:0]  vertex1_primary_b      ,
    output reg  [7:0]  vertex1_primary_a      ,
    output reg  [31:0] vertex1_fog_x          ,
    output reg  [31:0] vertex1_fog_y          ,
    output reg  [31:0] vertex1_fog_z          ,
    output reg  [31:0] vertex1_fog_w          ,
    output reg  [47:0] vertex2_x               ,
    output reg  [47:0] vertex2_y               ,
    output reg  [47:0] vertex2_z               ,
    output reg  [47:0] vertex2_w               ,
    output reg  [31:0] vertex2_s0              ,
    output reg  [31:0] vertex2_t0              ,
    output reg  [31:0] vertex2_r0              ,
    output reg  [31:0] vertex2_q0              ,
    output reg  [7:0]  vertex2_primary_r       ,
    output reg  [7:0]  vertex2_primary_g      ,
    output reg  [7:0]  vertex2_primary_b      ,
    output reg  [7:0]  vertex2_primary_a      ,
    output reg  [31:0] vertex2_fog_x          ,
    output reg  [31:0] vertex2_fog_y          ,
    output reg  [31:0] vertex2_fog_z          ,
    output reg  [31:0] vertex2_fog_w          ,
    input [31:0]					 x_out,
    input [31:0]					 y_out,
    input [31:0]                    z_out,
    input 						    xy_out_en,
    input [7:0]  primary_r                ,
    input [7:0]  primary_g                ,
    input [7:0]  primary_b                ,
    input [7:0]  primary_a                ,
    input [31:0] in_s0                       ,
    input [31:0] in_t0                       ,
    input  fragment_gen_end               ,
    output reg test_end                       ,
    input bte_busy

);
logic [47:0] v0x;
logic [47:0] v0y; 
logic [47:0] v1x;
logic [47:0] v1y;
logic [47:0] v2x;
logic [47:0] v2y;
logic [47:0] v0z;
logic [47:0] v1z; 
logic [47:0] v2z;
logic [7:0]  v0r;
logic [7:0]  v0g; 
logic [7:0]  v0b; 
logic [7:0]  v0a;
logic [7:0]  v1r;
logic [7:0]  v1g; 
logic [7:0]  v1b; 
logic [7:0]  v1a; 
logic [7:0]  v2r;
logic [7:0]  v2g; 
logic [7:0]  v2b; 
logic [7:0]  v2a;
logic [31:0] v0s;
logic [31:0] v0t;  
logic [31:0] v1s;
logic [31:0] v1t;  
logic [31:0] v2s;
logic [31:0] v2t;  
logic [63:0] area;
logic [47:0] v0w;
logic [47:0] v1w;
logic [47:0] v2w;


logic [31:0] cur_tile_x;
logic [31:0] cur_tile_y;
logic [47:0] x0;
logic [47:0] y0;
logic [47:0] x1;
logic [47:0] y1;  
logic [47:0] x2;
logic [47:0] y2; 
logic [47:0] ee_a0;
logic [47:0] ee_b0;
logic [47:0] ee_a1;
logic [47:0] ee_b1;  
logic [47:0] ee_a2;
logic [47:0] ee_b2;
logic [47:0] w0;
logic [47:0] w1;   
logic [47:0] w2;   
logic [47:0] z0;
logic [7:0]  r0;
logic [7:0]  g0;
logic [7:0]  b0;
logic [7:0]  a0; 
logic [31:0] s0; 
logic [31:0] t0; 
logic [47:0] z1;
logic [7:0]  r1;
logic [7:0]  g1;
logic [7:0]  b1;
logic [7:0]  a1; 
logic [31:0] s1; 
logic [31:0] t1;
logic [47:0] z2;
logic [7:0]  r2;
logic [7:0]  g2;
logic [7:0]  b2;
logic [7:0]  a2; 
logic [31:0] s2; 
logic [31:0] t2;
logic [95:0] ee0_int;
logic [95:0] ee1_int; 
logic [95:0] ee2_int; 
logic judge_t0;
logic judge_t1; 
logic judge_t2;
logic [3:0] x_temp;
logic [3:0] y_temp;
logic [95:0] cur_ee0;
logic [95:0] cur_ee1; 
logic [95:0] cur_ee2;
logic [31:0] cur_x;
logic [31:0] cur_y;

logic [7:0] cur_r;
logic [7:0] cur_g; 
logic [7:0] cur_b; 
logic [7:0] cur_a; 
logic [31:0] cur_z; 
logic [31:0] cur_w; 
logic [31:0] cur_s; 
logic [31:0] cur_t; 
reg [63:0] tile_cor_buffer [63:0];
reg [863:0] vertex_buffer [1023:0];
reg [191:0] pixel_buffer [20000000:0];

reg [191:0] pixel_buffer2 [20000000:0]; 

reg [31:0] vertex_count;
reg [31:0] tile_count;

reg error;

reg error_high;
reg error_z;
reg [31:0] pixel_in_counter;

wire [191:0] data_true = pixel_buffer[pixel_in_counter];
reg test_begin;

wire rst_n = ~test_begin & rst_n_in; 

reg [31:0] max_diff_s;
reg [31:0] max_diff_t;



wire [31:0] s_diff = ($signed(data_true[159:128]) > $signed(in_s0)) ? $signed(data_true[159:128]) - $signed(in_s0) : $signed(in_s0) - $signed(data_true[159:128]);
wire [31:0] t_diff = ($signed(data_true[191:160]) > $signed(in_t0)) ? $signed(data_true[191:160]) - $signed(in_t0) : $signed(in_t0) - $signed(data_true[191:160]);  
wire [31:0] z_diff = ($signed(data_true[95:64]) > $signed(z_out)) ? $signed(data_true[95:64]) - $signed(z_out) : $signed(z_out) - $signed(data_true[95:64]);  
 
always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           error <= 0;
           pixel_in_counter <= 0;

        end
       else if(xy_out_en)
        begin
            if({data_true[127:96],data_true[63:0]} !=  {primary_r,primary_g,primary_b,primary_a,y_out,x_out})
                begin
                    error <= 1;
                   // $display("error pixel : %d \n",pixel_in_counter);
                end
            else
                error <= 0;
            pixel_in_counter <= pixel_in_counter + 1;
        end
    end


always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           error_z <= 0;

        end
       else if(xy_out_en)
        begin
            if(z_diff > 32'h10) 
                begin
                    error_z <= 1;
                end
            else
                error_z <= 0;
        end
    end  
always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           max_diff_s <= 0;

        end
       else if(xy_out_en)
        begin
            if( s_diff >max_diff_s)
                begin
                    max_diff_s <= s_diff;
                end
        end
    end  

always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           max_diff_t <= 0;

        end
       else if(xy_out_en)
        begin
            if( t_diff >max_diff_t)
                begin
                    max_diff_t <= t_diff;
                end
        end
    end 

always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           error_high <= 0;

        end
       else if(xy_out_en)
        begin
            if( (s_diff > 32'h200 || t_diff > 32'h200))
                begin
                    error_high <= 1;
                end
            else
                error_high <= 0;
        end
    end   

always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
        begin
           vertex_count <= 0;
           tile_count <= 0;
           test_end <= 0; 
        end
       else if(bte_start)
        begin
            if(vertex_count == 32'd511 && tile_count == 32'd4095)
            begin
                vertex_count <= 0;
                tile_count <= 0;
                test_end <= 1; 
            end     
            else if(vertex_count == 32'd511)
                begin
                   tile_count <= tile_count + 1;
                   vertex_count <= 0;
                end
            else
                begin
                   vertex_count <= vertex_count + 1'b1;
                end  
        end
    end

always@(posedge clk or negedge rst_n)
    begin
       if(~rst_n)
            begin
                bte_start <= 0;
                tile_x    <= 0;
                tile_y    <= 0;                         
                vertex0_x <= 48'h0;              
                vertex0_y <= 48'h0;              
                vertex1_x <= 48'h0;              
                vertex1_y <= 48'h0;                
                vertex2_x <= 48'h0;              
                vertex2_y <= 48'h0;
                vertex0_z           <=  48'b0;  
                vertex0_w           <=  48'b0;  
                vertex0_s0          <=  48'b0;  
                vertex0_t0          <=  48'b0;  
                vertex0_r0          <=  48'b0;  
                vertex0_q0          <=  48'b0;  
                vertex0_primary_r   <=  48'b0;  
                vertex0_primary_g   <=  48'b0;  
                vertex0_primary_b   <=  48'b0;  
                vertex0_primary_a   <=  48'b0;  
                vertex0_fog_x       <=  48'b0;  
                vertex0_fog_y       <=  48'b0;  
                vertex0_fog_z       <=  48'b0;  
                vertex0_fog_w       <=  48'b0;  
                vertex1_z           <=  48'b0;  
                vertex1_w           <=  48'b0;  
                vertex1_s0          <=  48'b0;  
                vertex1_t0          <=  48'b0;  
                vertex1_r0          <=  48'b0;  
                vertex1_q0          <=  48'b0;  
                vertex1_primary_r   <=  48'b0;  
                vertex1_primary_g   <=  48'b0;  
                vertex1_primary_b   <=  48'b0;  
                vertex1_primary_a   <=  48'b0;  
                vertex1_fog_x       <=  48'b0;  
                vertex1_fog_y       <=  48'b0;  
                vertex1_fog_z       <=  48'b0;  
                vertex1_fog_w       <=  48'b0;  
                vertex2_z           <=  48'b0;  
                vertex2_w           <=  48'b0;  
                vertex2_s0          <=  48'b0;  
                vertex2_t0          <=  48'b0;  
                vertex2_r0          <=  48'b0;  
                vertex2_q0          <=  48'b0;  
                vertex2_primary_r   <=  48'b0;  
                vertex2_primary_g   <=  48'b0;  
                vertex2_primary_b   <=  48'b0;  
                vertex2_primary_a   <=  48'b0;  
                vertex2_fog_x       <=  48'b0;  
                vertex2_fog_y       <=  48'b0;  
                vertex2_fog_z       <=  48'b0;  
                vertex2_fog_w       <=  48'b0;  
            end
        else if(~bte_busy && ~test_end && ~bte_start)
            begin
                bte_start <= 1;
                `ifdef TEST_FIRST
                     {vertex0_z,vertex1_z,vertex2_z,vertex0_primary_r,vertex0_primary_g,vertex0_primary_b,vertex0_primary_a,vertex1_primary_r,vertex1_primary_g,vertex1_primary_b,vertex1_primary_a,vertex2_primary_r,vertex2_primary_g,vertex2_primary_b,vertex2_primary_a,vertex0_s0,vertex0_t0,vertex1_s0,vertex1_t0,vertex2_s0,vertex2_t0,vertex2_y,vertex2_x,vertex1_y,vertex1_x,vertex0_y,vertex0_x} <= vertex_buffer[0];
                     vertex0_w = -vertex0_z;
                     vertex1_w = -vertex1_z;
                     vertex2_w = -vertex2_z;
                     tile_y <= 0; 
                     tile_x <= 32'h700000; 
                `else
                {vertex0_w,vertex1_w,vertex2_w,vertex0_z,vertex1_z,vertex2_z,vertex0_primary_r,vertex0_primary_g,vertex0_primary_b,vertex0_primary_a,vertex1_primary_r,vertex1_primary_g,vertex1_primary_b,vertex1_primary_a,vertex2_primary_r,vertex2_primary_g,vertex2_primary_b,vertex2_primary_a,vertex0_s0,vertex0_t0,vertex1_s0,vertex1_t0,vertex2_s0,vertex2_t0,vertex2_y,vertex2_x,vertex1_y,vertex1_x,vertex0_y,vertex0_x} <= vertex_buffer[vertex_count];
                if(vertex_count == 32'd511)
                begin
                if(tile_x == 32'h3f00000 && tile_y == 32'h3f00000)
                    begin
                       tile_y <= 0; 
                       tile_x <= 0; 
                    end                
                else if(tile_x == 32'h3f00000)
                    begin
                       tile_y <= tile_y + 32'h100000; 
                       tile_x <= 0; 
                    end
                else 
                    begin
                        tile_x <= tile_x + 32'h100000;
                    end
                end
                `endif
            end
        else
            begin
                bte_start <= 0;
            end
    end

always@(posedge clk or negedge rst_n)
    begin
        if(~rst_n)
            busy <= 0;
        else
            busy <= $urandom_range(1'b0,1'b1);
    end



integer i;
integer j;
integer k;
integer m;
integer n;   
integer pixel_count;
//initial tile coordinate,rang from 0 - 1024, 16 pixel align
initial
begin
   for(m=0;m<64;m=m+1)
   begin
        tile_cor_buffer[m][31:0] = {$urandom_range(12'h0,12'h40),20'b0} ;
        tile_cor_buffer[m][63:32] = {$urandom_range(12'h0,12'h40),20'b0} ; 
        end
end

//
initial
begin
  for(n=0;n<1024;n=n+1)
  begin
        v0x= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)}; 
        v0y= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)};
        v1x= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)}; 
        v1y= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)}; 
        v2x= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)}; 
        v2y= {$urandom_range(48'h0,48'h4000000)};//48'hffffffffffff)};
        v0w= {$urandom_range(48'h0,48'h4000000)};
        v1w= {$urandom_range(48'h0,48'h4000000)}; 
        v2w= {$urandom_range(48'h0,48'h4000000)}; 
        v0z= {$urandom_range(48'h0,48'h4000000)};
        v1z= {$urandom_range(48'h0,48'h4000000)}; 
        v2z= {$urandom_range(48'h0,48'h4000000)};
        v0r= {$urandom_range(8'h0,8'hff)};
        v0g= {$urandom_range(8'h0,8'hff)}; 
        v0b= {$urandom_range(8'h0,8'hff)}; 
        v0a= {$urandom_range(8'h0,8'hff)};
        v1r= {$urandom_range(8'h0,8'hff)};
        v1g= {$urandom_range(8'h0,8'hff)}; 
        v1b= {$urandom_range(8'h0,8'hff)}; 
        v1a= {$urandom_range(8'h0,8'hff)}; 
        v2r= {$urandom_range(8'h0,8'hff)};
        v2g= {$urandom_range(8'h0,8'hff)}; 
        v2b= {$urandom_range(8'h0,8'hff)}; 
        v2a= {$urandom_range(8'h0,8'hff)};
        v0s= {$urandom_range(32'h0,32'hffffffff)}; 
        v0t= {$urandom_range(32'h0,32'hffffffff)};  
        v1s= {$urandom_range(32'h0,32'hffffffff)};
        v1t= {$urandom_range(32'h0,32'hffffffff)};  
        v2s= {$urandom_range(32'h0,32'hffffffff)};
        v2t= {$urandom_range(32'h0,32'hffffffff)};  
        area = (v1x - v0x) * (v2y - v0y) + (v2x - v0x) * (v1y - v0y);
        if(area > 0)
           vertex_buffer[n] = {v0w,v1w,v2w,v0z,v1z,v2z,v0r,v0g,v0b,v0a,v1r,v1g,v1b,v1a,v2r,v2g,v2b,v2a,v0s,v0t,v1s,v1t,v2s,v2t,v2y,v2x,v1y,v1x,v0y,v0x};
        else
           vertex_buffer[n] = {v0w,v1w,v2w,v0z,v1z,v2z,v0r,v0g,v0b,v0a,v1r,v1g,v1b,v1a,v2r,v2g,v2b,v2a,v0s,v0t,v1s,v1t,v2s,v2t,v1y,v1x,v2y,v2x,v0y,v0x}; 
  end
end

real s2dw;
real s0dw; 
real s1dw; 
real t2dw;
real t0dw; 
real t1dw; 

real w0_rcp;
real w1_rcp;
real w2_rcp;

real test_s;
real test_t;
real test_w;

real s_d_z;

logic [96+8-1:0] test1;
logic [95:0] area;

logic [31:0] k1;
logic [31:0] k2;
shortreal k1_float;
shortreal k2_float;
shortreal s2_real;
shortreal s0_real; 
shortreal s1_real; 
shortreal t2_real;
shortreal t0_real; 
shortreal t1_real;
shortreal w2_real;
shortreal w0_real; 
shortreal w1_real;
shortreal cur_ee0_real;
shortreal cur_ee1_real;
shortreal cur_ee2_real;
shortreal area_real;
shortreal s0ds2;
shortreal s1ds2;
shortreal k1s0;
shortreal k2s1;
shortreal inter_sum;
shortreal test_s_2;
shortreal diff_2;




initial
begin
    pixel_count = 0;
    test_begin = 0;
    `ifdef TEST_FIRST
       cur_tile_x = (0%64)*16*65536;
       cur_tile_y = (0/64)*16*65536;
         for(j=0;j<511;j=j+1)
            begin
                {w0,w1,w2,z0,z1,z2,r0,g0,b0,a0,r1,g1,b1,a1,r2,g2,b2,a2,s0,t0,s1,t1,s2,t2,y2,x2,y1,x1,y0,x0} = vertex_buffer[j];
                //x0 = 0;
                //y0 = 0;
                //x1 = 16*65536;
                //y1 = 16*65536;
                //x2 = 0;
                //y2 = 16*65536;
	            ee_a0 = y0- y1;
	            ee_b0 = x1- x0;
	            ee_a1 = y1- y2;
	            ee_b1 = x2- x1;
	            ee_a2 = y2- y0;
	            ee_b2 = x0- x2;
	            ee0_int =$signed(ee_a0) *$signed(cur_tile_x) + $signed(ee_b0) * $signed(cur_tile_y) + $signed(x0) * $signed(y1) - $signed(x1) * $signed(y0);
	            ee1_int =$signed(ee_a1) *$signed(cur_tile_x) + $signed(ee_b1) * $signed(cur_tile_y) + $signed(x1) * $signed(y2) - $signed(x2) * $signed(y1);
	            ee2_int =$signed(ee_a2) *$signed(cur_tile_x) + $signed(ee_b2) * $signed(cur_tile_y) + $signed(x2) * $signed(y0) - $signed(x0) * $signed(y2); 

                judge_t0 = (~ee_a0[47] ) | ( (a0 == 0) & (b0 > 0) );
	            judge_t1 = (~ee_a1[47] ) | ( (a1 == 0) & (b1 > 0) );
                judge_t2 = (~ee_a2[47] ) | ( (a2 == 0) & (b2 > 0) );

                for(k=0;k<256;k=k+1)
                    begin
                        x_temp= k%2 + ((k & 4)>>2)*2 + ((k & 16)>>4)*4 + ((k & 64)>>6)*8 ;
		                y_temp=((k & 2)>>1) + ((k & 8)>>3)*2 + ((k & 32)>>5)*4 + ((k & 128)>>7)*8 ;
                        w0 = 2**32/w0;
                        w1 = 2**32/w1;
                        w2 = 2**32/w2;
	                    cur_ee0 = $signed(ee0_int) +$signed(ee_a0) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b0) * $signed(y_temp*65536 + 65536/2);
		                cur_ee1 = $signed(ee1_int) +$signed(ee_a1) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b1) * $signed(y_temp*65536 + 65536/2);
		                cur_ee2 = $signed(ee2_int) +$signed(ee_a2) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b2) * $signed(y_temp*65536 + 65536/2);
                        if((~cur_ee0[95] || (judge_t0 && cur_ee0 == 0)) & (~cur_ee1[95] || (judge_t1 && cur_ee1 == 0)) & (~cur_ee2[95] || (judge_t2 && cur_ee2 == 0))) 
                            begin
                                cur_x = cur_tile_x + x_temp* 65536;
                                cur_y = cur_tile_y + y_temp* 65536;
                                cur_r = (cur_ee0 * r2 + cur_ee1 * r0 + cur_ee2 * r1)/(cur_ee0 + cur_ee1 + cur_ee2);
                                cur_g = (cur_ee0 * g2 + cur_ee1 * g0 + cur_ee2 * g1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_b = (cur_ee0 * b2 + cur_ee1 * b0 + cur_ee2 * b1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_a = (cur_ee0 * a2 + cur_ee1 * a0 + cur_ee2 * a1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_z = (cur_ee0 * z2 + cur_ee1 * z0 + cur_ee2 * z1)/(cur_ee0 + cur_ee1 + cur_ee2);
                                ee0xs2 = $signed(cur_ee0) * ($signed({s2,16'b0})/$signed(w2));
                                ee1xs0 = $signed(cur_ee0) * ($signed({s0,16'b0})/$signed(w0)); 
                                ee2xs1 = $signed(cur_ee2) * ($signed({s1,16'b0})/$signed(w1)); 
                                ee0xt2 = $signed(cur_ee0) * ($signed({t2,16'b0})/$signed(w2));
                                ee1xt0 = $signed(cur_ee1) * ($signed({t0,16'b0})/$signed(w0)); 
                                ee2xt1 = $signed(cur_ee2) * ($signed({t1,16'b0})/$signed(w1)); 
                                
 
                                cur_s = ($signed(ee0xs2) + $signed(ee1xs0)  + $signed(ee2xs1))/(($signed(-cur_ee0*65536) /$signed(z2)) + ($signed(-cur_ee1*65536) /$signed(z0))  + ($signed(-cur_ee2*65536) /$signed(z1)));
                                cur_t = ($signed(ee0xt2) + $signed(ee1xt0)  + $signed(ee2xt1))/(($signed(-cur_ee0*65536) /$signed(z2)) + ($signed(-cur_ee1*65536) /$signed(z0))  + ($signed(-cur_ee2*65536) /$signed(z1)));
                                pixel_buffer[pixel_count] = {cur_t,cur_s,cur_r,cur_g,cur_b,cur_a,cur_z,cur_y,cur_x};
                                pixel_count = pixel_count + 1;
                                k=256;
                            end
                    end
            end  
    `else
#10
   for(i=0;i<4096;i=i+1)
    begin

       cur_tile_x = (i%64)*16*65536;
       cur_tile_y = (i/64)*16*65536;
         for(j=0;j<511;j=j+1)
            begin
               {w0,w1,w2,z0,z1,z2,r0,g0,b0,a0,r1,g1,b1,a1,r2,g2,b2,a2,s0,t0,s1,t1,s2,t2,y2,x2,y1,x1,y0,x0} = vertex_buffer[j];
	            ee_a0 = y0- y1;
	            ee_b0 = x1- x0;
	            ee_a1 = y1- y2;
	            ee_b1 = x2- x1;
	            ee_a2 = y2- y0;
	            ee_b2 = x0- x2;
	            ee0_int =$signed(ee_a0) *$signed(cur_tile_x) + $signed(ee_b0) * $signed(cur_tile_y) + $signed(x0) * $signed(y1) - $signed(x1) * $signed(y0);
	            ee1_int =$signed(ee_a1) *$signed(cur_tile_x) + $signed(ee_b1) * $signed(cur_tile_y) + $signed(x1) * $signed(y2) - $signed(x2) * $signed(y1);
	            ee2_int =$signed(ee_a2) *$signed(cur_tile_x) + $signed(ee_b2) * $signed(cur_tile_y) + $signed(x2) * $signed(y0) - $signed(x0) * $signed(y2); 

                judge_t0 = (~ee_a0[47] ) | ( (a0 == 0) & (b0 > 0) );
	            judge_t1 = (~ee_a1[47] ) | ( (a1 == 0) & (b1 > 0) );
                judge_t2 = (~ee_a2[47] ) | ( (a2 == 0) & (b2 > 0) );
                 
                for(k=0;k<256;k=k+1)
                    begin
                        x_temp= k%2 + ((k & 4)>>2)*2 + ((k & 16)>>4)*4 + ((k & 64)>>6)*8 ;
		                y_temp=((k & 2)>>1) + ((k & 8)>>3)*2 + ((k & 32)>>5)*4 + ((k & 128)>>7)*8 ;
	                    cur_ee0 = $signed(ee0_int) +$signed(ee_a0) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b0) * $signed(y_temp*65536 + 65536/2);
		                cur_ee1 = $signed(ee1_int) +$signed(ee_a1) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b1) * $signed(y_temp*65536 + 65536/2);
		                cur_ee2 = $signed(ee2_int) +$signed(ee_a2) *$signed(x_temp*65536 + 65536/2) +$signed( ee_b2) * $signed(y_temp*65536 + 65536/2);
                        if((~cur_ee0[95] || (judge_t0 && cur_ee0 == 0)) & (~cur_ee1[95] || (judge_t1 && cur_ee1 == 0)) & (~cur_ee2[95] || (judge_t2 && cur_ee2 == 0)))
                            begin
                                cur_x = cur_tile_x + x_temp* 65536;
                                cur_y = cur_tile_y + y_temp* 65536;
                                cur_r = (cur_ee0 * r2 + cur_ee1 * r0 + cur_ee2 * r1)/(cur_ee0 + cur_ee1 + cur_ee2);
                                cur_g = (cur_ee0 * g2 + cur_ee1 * g0 + cur_ee2 * g1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_b = (cur_ee0 * b2 + cur_ee1 * b0 + cur_ee2 * b1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_a = (cur_ee0 * a2 + cur_ee1 * a0 + cur_ee2 * a1)/(cur_ee0 + cur_ee1 + cur_ee2);  
                                cur_z = ($signed(cur_ee0) * $signed(z2) + $signed(cur_ee1) * $signed(z0) + $signed(cur_ee2) * $signed(z1))/$signed(cur_ee0 + cur_ee1 + cur_ee2);
                                area = cur_ee0 + cur_ee1 + cur_ee2;
                                k1 = cur_ee1*(2**32)/(cur_ee0 + cur_ee1 + cur_ee2);
                                k2 = cur_ee2*(2**32)/(cur_ee0 + cur_ee1 + cur_ee2);
                                s2_real = $signed(s2);
                                s0_real = $signed(s0); 
                                s1_real = $signed(s1); 
                                t2_real = $signed(t2);
                                t0_real = $signed(t0); 
                                t1_real = $signed(t1);
                                w2_real = $signed(w2);
                                w0_real = $signed(w0); 
                                w1_real = $signed(w1); 
                                s2dw = s2_real/w2_real;
                                s0dw = s0_real/w0_real; 
                                s1dw = s1_real/w1_real; 
                                t2dw = t2_real/w2_real;
                                t0dw = t0_real/w0_real; 
                                t1dw = t1_real/w1_real; 
                                cur_ee0_real = cur_ee0;
                                cur_ee1_real = cur_ee1;
                                cur_ee2_real = cur_ee2;
                                area_real = area;

                                k1_float =cur_ee1_real/area_real;
                                k2_float =cur_ee2_real/area_real;
                                w0_rcp = (1.0/w0_real);
                                w1_rcp = (1.0/w1_real);
                                w2_rcp = (1.0/w2_real);
                                s0ds2 =  (s0dw - s2dw);
                                s1ds2 =  s1dw - s2dw;
                                k1s0 = s0ds2 * k1_float;
                                k2s1 = s1ds2 * k2_float;
                                inter_sum = k1s0 + k2s1;
                                test_s = s2dw + inter_sum;//k1_float * (s0dw - s2dw) + k2_float * (s1dw - s2dw);
                                test_t = t2dw + k1_float * (t0dw - t2dw) + k2_float * (t1dw - t2dw);
                                test_w = w2_rcp + k1_float * (w0_rcp -w2_rcp) + k2_float * (w1_rcp - w2_rcp);
                                cur_s = test_s/test_w ;
                                cur_t = test_t/test_w ;
                                test_s_2 = (cur_ee0_real * s2_real/w2_real + cur_ee1_real * s0_real/w0_real + cur_ee2_real * s1_real/w1_real)/(cur_ee0_real/w2_real + cur_ee1_real/w0_real + cur_ee2_real /w1_real);
                                //diff_2 = test_s/test_w  - test_s_2;
                                pixel_buffer[pixel_count] = {cur_t,cur_s,cur_r,cur_g,cur_b,cur_a,cur_z,cur_y,cur_x};
                                cur_s = (cur_ee0_real * s2_real/w2_real + cur_ee1_real * s0_real/w0_real + cur_ee2_real * s1_real/w1_real)/(cur_ee0_real/w2_real + cur_ee1_real/w0_real + cur_ee2_real /w1_real);
                                cur_t = (cur_ee0_real * t2_real/w2_real + cur_ee1_real * t0_real/w0_real + cur_ee2_real * t1_real/w1_real)/(cur_ee0_real/w2_real + cur_ee1_real/w0_real + cur_ee2_real /w1_real);
                                pixel_buffer2[pixel_count] = {cur_t,cur_s,cur_r,cur_g,cur_b,cur_a,cur_z,cur_y,cur_x}; 
                                pixel_count = pixel_count + 1; 
                                #10;
                                
                                
                            end
                    end
            end
    end
    `endif
    test_begin = 1;
end

wire [255:0] test_buffer = tile_cor_buffer[0];

wire [31:0] ee1_bit = $shortrealtobits(cur_ee1);
wire [31:0] k1_bit = $shortrealtobits(k1_float);
wire [31:0] k2_bit = $shortrealtobits(k2_float); 
wire [31:0] s2dw_bit = $shortrealtobits(s2dw);
wire [31:0] s0dw_bit = $shortrealtobits(s0dw); 
wire [31:0] s1dw_bit = $shortrealtobits(s1dw); 
wire [31:0] t2dw_bit = $shortrealtobits(t2dw);
wire [31:0] t0dw_bit = $shortrealtobits(t0dw); 
wire [31:0] t1dw_bit = $shortrealtobits(t1dw);
wire [31:0] s0ds2_bit  = $shortrealtobits(s0ds2 );
wire [31:0] s1ds2_bit  = $shortrealtobits(s1ds2 );
wire [31:0] k1s0_bit   = $shortrealtobits(k1s0  );
wire [31:0] k2s1_bit   = $shortrealtobits(k2s1  );
wire [31:0] inter_sum_bit = $shortrealtobits(inter_sum);
wire [31:0] test_s_bit = $shortrealtobits(test_s);
wire [31:0] w_bit =  $shortrealtobits(test_w);


real error_s;
real error_t;  
real dx_01;
real dx_02;
real dx_12;
real dy_01;
real dy_02;
real dy_12; 
real ds_01;
real ds_02;
real ds_12;
real s_error_rate_dx_01;
real s_error_rate_dx_02; 
real s_error_rate_dx_12; 
real s_error_rate_dy_01;
real s_error_rate_dy_02; 
real s_error_rate_dy_12;
real dt_01;
real dt_02;
real dt_12;
real t_error_rate_dx_01;
real t_error_rate_dx_02; 
real t_error_rate_dx_12; 
real t_error_rate_dy_01;
real t_error_rate_dy_02; 
real t_error_rate_dy_12;

reg error_rate_high_resolution;
reg error_rate_high;
real s_error_rate_d01;
real s_error_rate_d02; 
real s_error_rate_d12; 
real t_error_rate_d01;
real t_error_rate_d02; 
real t_error_rate_d12; 
initial
begin
    error_rate_high = 0;
    error_rate_high_resolution = 0;
    while(1)
    wait(xy_out_en)
    begin
        #5;
        error_s = s_diff;
        dx_01 = real'($signed(vertex0_x) - $signed(vertex1_x))/2**16;
        dx_02 = real'($signed(vertex0_x) - $signed(vertex2_x))/2**16;
        dx_12 = real'($signed(vertex1_x) - $signed(vertex2_x))/2**16;
        dy_01 = real'($signed(vertex0_y) - $signed(vertex1_y))/2**16;
        dy_02 = real'($signed(vertex0_y) - $signed(vertex2_y))/2**16;
        dy_12 = real'($signed(vertex1_y) - $signed(vertex2_y))/2**16; 
        ds_01 = real'($signed(vertex0_s0) - $signed(vertex1_s0));
        ds_02 = real'($signed(vertex0_s0) - $signed(vertex2_s0));
        ds_12 = real'($signed(vertex1_s0) - $signed(vertex2_s0)); 
        s_error_rate_dx_01 =  error_s/(ds_01/dx_01);
        s_error_rate_dx_02 =  error_s/(ds_02/dx_02);
        s_error_rate_dx_12 =  error_s/(ds_12/dx_12);
        s_error_rate_dy_01 =  error_s/(ds_01/dy_01);
        s_error_rate_dy_02 =  error_s/(ds_02/dy_02);
        s_error_rate_dy_12 =  error_s/(ds_12/dy_12);
        s_error_rate_d01 =  error_s/(ds_01);
        s_error_rate_d02 =  error_s/(ds_02);
        s_error_rate_d12 =  error_s/(ds_12); 
        error_t = t_diff;
        dx_01 = real'($signed(vertex0_x) - $signed(vertex1_x))/2**16;
        dx_02 = real'($signed(vertex0_x) - $signed(vertex2_x))/2**16;
        dx_12 = real'($signed(vertex1_x) - $signed(vertex2_x))/2**16;
        dy_01 = real'($signed(vertex0_y) - $signed(vertex1_y))/2**16;
        dy_02 = real'($signed(vertex0_y) - $signed(vertex2_y))/2**16;
        dy_12 = real'($signed(vertex1_y) - $signed(vertex2_y))/2**16; 
        dt_01 = real'($signed(vertex0_t0) - $signed(vertex1_t0));
        dt_02 = real'($signed(vertex0_t0) - $signed(vertex2_t0));
        dt_12 = real'($signed(vertex1_t0) - $signed(vertex2_t0)); 
        t_error_rate_dx_01 =  error_t/(dt_01/dx_01);
        t_error_rate_dx_02 =  error_t/(dt_02/dx_02);
        t_error_rate_dx_12 =  error_t/(dt_12/dx_12);
        t_error_rate_dy_01 =  error_t/(dt_01/dy_01);
        t_error_rate_dy_02 =  error_t/(dt_02/dy_02);
        t_error_rate_dy_12 =  error_t/(dt_12/dy_12);
        t_error_rate_d01 =  error_t/(dt_01);
        t_error_rate_d02 =  error_t/(dt_02);
        t_error_rate_d12 =  error_t/(dt_12);
        #1;
        //$display("error rate : %e\n%e\n%e\n%e\n%e\n%e\n%e\n%e\n%e\n%e\n%e\n%e\n",s_error_rate_dx_01,
        //s_error_rate_dx_02,
        //s_error_rate_dx_12,
        //s_error_rate_dy_01,
        //s_error_rate_dy_02,
        //s_error_rate_dy_12,
        //t_error_rate_dx_01,
        //t_error_rate_dx_02,
        //t_error_rate_dx_12,
        //t_error_rate_dy_01,
        //t_error_rate_dy_02,
        //t_error_rate_dy_12);
        if(xy_out_en && ((s_error_rate_dx_01>0.05 || s_error_rate_dx_01 < -0.05)
                       ||(s_error_rate_dx_12>0.05 || s_error_rate_dx_12 < -0.05)
                       ||(s_error_rate_dx_02>0.05 || s_error_rate_dx_02 < -0.05)
                       ||(s_error_rate_dy_01>0.05 || s_error_rate_dy_01 < -0.05)
                       ||(s_error_rate_dy_12>0.05 || s_error_rate_dy_12 < -0.05)
                       ||(s_error_rate_dy_02>0.05 || s_error_rate_dy_02 < -0.05)
                       ||(t_error_rate_dx_01>0.05 || t_error_rate_dx_01 < -0.05)
                       ||(t_error_rate_dx_12>0.05 || t_error_rate_dx_12 < -0.05)
                       ||(t_error_rate_dx_02>0.05 || t_error_rate_dx_02 < -0.05)
                       ||(t_error_rate_dy_01>0.05 || t_error_rate_dy_01 < -0.05)
                       ||(t_error_rate_dy_12>0.05 || t_error_rate_dy_12 < -0.05)
                       ||(t_error_rate_dy_02>0.05 || t_error_rate_dy_02 < -0.05)  )
         )
        begin
         error_rate_high_resolution = 1;
         $display("error resolution rate high at pixel %d\n",pixel_in_counter);
        end
         else
         error_rate_high_resolution = 0;
        if(xy_out_en && ((s_error_rate_d01>0.01 || s_error_rate_d01 < -0.01)
                        ||(s_error_rate_d12>0.01 || s_error_rate_d12 < -0.01)
                        ||(s_error_rate_d02>0.01 || s_error_rate_d02 < -0.01)
                        ||(t_error_rate_d01>0.01 || t_error_rate_d01 < -0.01)
                        ||(t_error_rate_d12>0.01 || t_error_rate_d12 < -0.01)
                        ||(t_error_rate_d02>0.01 || t_error_rate_d02 < -0.01)
         ))
        begin
         error_rate_high = 1;
         $display("error rate high at pixel %d\n",pixel_in_counter);
        end
         else
         error_rate_high = 0; 
    #4;
    end
end


endmodule                                                           
